package cn.minhx.domain.activity.service.trial.node;

import static cn.minhx.types.enums.ResponseCode.E0001;

import cn.minhx.domain.activity.model.entity.MarketProductEntity;
import cn.minhx.domain.activity.model.entity.TrialBalanceEntity;
import cn.minhx.domain.activity.model.valobj.GroupBuyActivityDiscountVO;
import cn.minhx.domain.activity.model.valobj.SkuVO;
import cn.minhx.domain.activity.service.discount.IDiscountCalculator;
import cn.minhx.domain.activity.service.trial.AbstractGroupBuyMarketSupport;
import cn.minhx.domain.activity.service.trial.factory.DefaultActivityStrategyFactory;
import cn.minhx.domain.activity.service.trial.task.QueryGroupBuyActivityDiscountVOTask;
import cn.minhx.domain.activity.service.trial.task.QuerySkuVOTask;
import cn.minhx.types.design.tree.StrategyHandler;
import cn.minhx.types.exception.AppException;
import com.alibaba.fastjson2.JSON;
import jakarta.annotation.Resource;
import java.math.BigDecimal;
import java.util.Map;
import java.util.concurrent.Future;
import java.util.concurrent.FutureTask;
import java.util.concurrent.ThreadPoolExecutor;
import java.util.concurrent.TimeUnit;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;

/**
 * 营销优惠试算节点
 *
 * @author minhx
 */
@Slf4j
@Service
public class MarketNode extends AbstractGroupBuyMarketSupport {

	@Resource
	private CrowdNode crowdNode;
	@Resource
	private ErrorNode errorNode;
	@Resource
	private ThreadPoolExecutor threadPoolExecutor;
	@Resource
	private Map<String, IDiscountCalculator> discountCalculatorMap;

	@Override
	protected void loadContext(MarketProductEntity requestParameter,
			DefaultActivityStrategyFactory.DynamicContext dynamicContext) throws Exception {
		log.info("营销优惠试算节点-loadContext requestParameter:{}", JSON.toJSONString(requestParameter));
		// .submit 自动封装为 Future， .execute 需要手动封装为 Future
		// 查询商品信息
		Future<SkuVO> querySkuVOFuture = threadPoolExecutor
				.submit(new QuerySkuVOTask(requestParameter.getGoodsId(), repository));
		// 查询活动配置
		QueryGroupBuyActivityDiscountVOTask queryGroupBuyActivityDiscountVOTask = new QueryGroupBuyActivityDiscountVOTask(
				requestParameter.getActivityId(), requestParameter.getSource(), requestParameter.getChannel(),
				requestParameter.getGoodsId(), repository);
		FutureTask<GroupBuyActivityDiscountVO> groupBuyActivityDiscountVOFutureTask = new FutureTask<>(
				queryGroupBuyActivityDiscountVOTask);
		threadPoolExecutor.execute(groupBuyActivityDiscountVOFutureTask);
		// 写入 context
		dynamicContext.setGroupBuyActivityDiscountVO(
				groupBuyActivityDiscountVOFutureTask.get(TASK_TIMOUT_SECONDS, TimeUnit.SECONDS));
		dynamicContext.setSkuVO(querySkuVOFuture.get(TASK_TIMOUT_SECONDS, TimeUnit.SECONDS));
		log.info("营销优惠试算节点-loadContext dynamicContext:{}", JSON.toJSONString(dynamicContext));
	}

	@Override
	protected TrialBalanceEntity doApply(MarketProductEntity requestParameter,
			DefaultActivityStrategyFactory.DynamicContext dynamicContext) throws Exception {
		log.info("营销优惠试算节点-doApply requestParameter:{} dynamicContext:{}", JSON.toJSONString(requestParameter),
				JSON.toJSONString(dynamicContext));
		// 优惠试算
		GroupBuyActivityDiscountVO.GroupBuyDiscount groupBuyDiscount = dynamicContext.getGroupBuyActivityDiscountVO()
				.getGroupBuyDiscount();
		SkuVO skuVO = dynamicContext.getSkuVO();
		IDiscountCalculator discountCalculator = discountCalculatorMap.get(groupBuyDiscount.getMarketPlan());
		if (null == discountCalculator) {
			log.info("不存在{}类型的折扣计算服务，当前支持类型为:{}", groupBuyDiscount.getMarketPlan(),
					JSON.toJSONString(discountCalculatorMap.keySet()));
			throw new AppException(E0001);
		}
		// 折扣价格
		BigDecimal discountedPrice = discountCalculator.calculate(requestParameter.getUserId(),
				skuVO.getOriginalPrice(), groupBuyDiscount);
		// 写入 context
		dynamicContext.setDiscountedPrice(discountedPrice);
		return router(requestParameter, dynamicContext);
	}

	@Override
	public StrategyHandler<MarketProductEntity, DefaultActivityStrategyFactory.DynamicContext, TrialBalanceEntity> next(
			MarketProductEntity requestParameter, DefaultActivityStrategyFactory.DynamicContext dynamicContext) {
		// 不存在配置的拼团活动，走异常节点
		if (null == dynamicContext.getGroupBuyActivityDiscountVO() || null == dynamicContext.getSkuVO()
				|| null == dynamicContext.getDiscountedPrice()) {
			return errorNode;
		}
		return crowdNode;
	}
}
